package com.czz.portal.controller;

import com.alipay.api.AlipayApiException;
import com.alipay.api.internal.util.AlipaySignature;
import com.czz.common.exception.CustomerException;
import com.czz.common.exception.ResultCodeEnum;
import com.czz.common.vo.R;
import com.czz.portal.config.AlipayConfig;
import com.czz.portal.entity.Course;
import com.czz.portal.entity.Order;
import com.czz.portal.service.CourseService;
import com.czz.portal.service.OrderService;
import com.czz.portal.service.PayService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.util.ObjectUtils;
import org.springframework.util.StringUtils;
import org.springframework.web.bind.annotation.*;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.UnsupportedEncodingException;
import java.util.Date;
import java.util.HashMap;
import java.util.Iterator;
import java.util.Map;

/**
 * @ClassName: PayController
 * @Author Czz
 * @Date 2020/2/10
 * @Time 9:57
 **/
@RestController
@RequestMapping(value = "/pay")
public class PayController {

    @Autowired
    PayService payService;

    @Autowired
    OrderService orderService;

    @Autowired
    CourseService courseService;
    /**
    * @Description 生成支付链接
    * @Param [orderId, request, response]
    * @Return com.czz.common.vo.R
    * @Author Czz
    * @Date 2020/2/10
    * @Time 11:38
    **/
    @PostMapping(value = "")
    public R PayByOrderId(String orderId, HttpServletRequest request, HttpServletResponse response){
        Order order = orderService.getById(orderId);
        String result = payService.createPay(order.getOrderId(),order.getCourseName(),order.getPayable(),"城院慕课课程订单");
        return R.ok().data("item",result);
    }

    /**
    * @Description 支付宝同步返回结果
    * @Param [request, response, map]
    * @Return com.czz.common.vo.R
    * @Author Czz
    * @Date 2020/2/10
    * @Time 13:07
    **/
    @RequestMapping(value = "/return_url")
    public String paySyncReturn(HttpServletRequest request, HttpServletResponse response){
        try {
            //获取支付宝GET过来反馈信息
            Map<String, String> params = new HashMap<String, String>();
            Map<String, String[]> requestParams = request.getParameterMap();
            for (Iterator<String> iter = requestParams.keySet().iterator(); iter.hasNext(); ) {
                String name = (String) iter.next();
                String[] values = (String[]) requestParams.get(name);
                String valueStr = "";
                for (int i = 0; i < values.length; i++) {
                    valueStr = (i == values.length - 1) ? valueStr + values[i]
                            : valueStr + values[i] + ",";
                }
                //乱码解决，这段代码在出现乱码时使用
                valueStr = new String(valueStr.getBytes("utf-8"), "utf-8");
                params.put(name, valueStr);
            }

            //调用SDK验证签名
            boolean signVerified = AlipaySignature.rsaCheckV1(params, AlipayConfig.alipay_public_key, AlipayConfig.charset, AlipayConfig.sign_type);

            //检验通过
            if (signVerified){
                // 同步返回结果，展示在前端
                String result = "<form action=\"http://localhost:5000/order\"  method=\"get\" name=\"form1\">\n" +
                "</form>\n" +
                "<script>document.forms[0].submit();</script>";
                 return result;
            }
            else {
                throw new CustomerException(ResultCodeEnum.CHECK_RSA_ERROR);
            }
        } catch (AlipayApiException | UnsupportedEncodingException e) {
            throw new CustomerException(ResultCodeEnum.CHECK_RSA_ERROR);
        }
    }

    @RequestMapping(value = "/notify_url")
    public R payAsyncReturn(HttpServletRequest request, HttpServletRequest response) throws AlipayApiException, UnsupportedEncodingException {
        //获取支付宝POST过来反馈信息
        Map<String, String> params = new HashMap<String, String>();
        Map<String, String[]> requestParams = request.getParameterMap();
        for (Iterator<String> iter = requestParams.keySet().iterator(); iter.hasNext(); ) {
            String name = (String) iter.next();
            String[] values = (String[]) requestParams.get(name);
            String valueStr = "";
            for (int i = 0; i < values.length; i++) {
                valueStr = (i == values.length - 1) ? valueStr + values[i]
                        : valueStr + values[i] + ",";
            }
            //乱码解决，这段代码在出现乱码时使用
            valueStr = new String(valueStr.getBytes("utf-8"), "utf-8");
            params.put(name, valueStr);
        }

        //调用SDK验证签名
        boolean signVerified = AlipaySignature.rsaCheckV1(params, AlipayConfig.alipay_public_key, AlipayConfig.charset, AlipayConfig.sign_type);

        //检验通过
        if (signVerified){
            //异步返回结果，操作数据库
            String orderId = request.getParameter("out_trade_no");
            String trade = request.getParameter("trade_no");
            String paid = request.getParameter("total_amount");

            //判断付款金额与应付金额是否一致
            Order order = orderService.getById(orderId);

            if (ObjectUtils.isEmpty(order)){
                return R.setResult(ResultCodeEnum.CREATE_PAY_ERROR);
            }

            if (!paid.equals(String.valueOf(order.getPayable()))){
                return R.setResult(ResultCodeEnum.CREATE_PAY_ERROR);
            }

            //order表写入流水号，支付时间，修改订单状态
            order.setTrade(trade);
            order.setPayTime(new Date());
            order.setStatus(1);

            //course表该课程购买数加一
            Course course = courseService.getById(order.getCourseId());
            course.setBuySum(course.getBuySum()+1);

            orderService.updateById(order);
            courseService.updateById(course);

            return R.ok();
        }
        else {
            throw new CustomerException(ResultCodeEnum.CHECK_RSA_ERROR);
        }
    }

    /**
    * @Description 根据订单号查询支付状态
    * @Param [orderId]
    * @Return com.czz.common.vo.R
    * @Author Czz
    * @Date 2020/2/10
    * @Time 17:55
    **/
    @GetMapping(value = "/query/{orderId}")
    public R queryPay(@PathVariable String orderId){
        if (StringUtils.isEmpty(orderId)){
            return R.setResult(ResultCodeEnum.INPUT_ERROR);
        }
        String result = payService.queryPay(orderId);
        // 返回结果的msg为Success，trade_status为TRADE_SUCCESS
        if (result.contains("Success") && result.contains("TRADE_SUCCESS")){
            return R.ok();
        }
        return R.setResult(ResultCodeEnum.PAY_ERROR);
    }
}
